<?php

namespace App\Http\Handler;

use App\Constants\Common\HttpStatusCode;
use Framework\MiddlewareRunner;
use GuzzleHttp\Psr7\Response;
use Psr\Http\Message\ServerRequestInterface;
use Psr\Http\Server\RequestHandlerInterface;
use Psr\Http\Message\ResponseInterface;

/**
 * Class CorsHandler
 * @package App\Http\Handler
 * @link https://developer.mozilla.org/zh-CN/docs/Web/HTTP/Access_control_CORS
 * @link https://annevankesteren.nl/2007/10/http-methods
 * @link https://fetch.spec.whatwg.org/#forbidden-header-name
 */
class CorsHandler implements RequestHandlerInterface
{
    protected $config;

    public function __construct($config)
    {
        $this->config = $config;
    }

    public function handle(ServerRequestInterface $request): ResponseInterface
    {
        if (false === strpos($this->config['allow-origin'], $_SERVER['HTTP_ORIGIN'])) {
            return MiddlewareRunner::next($request);
        }
        $origin = $_SERVER['HTTP_ORIGIN'];
        $headers = [
            'Access-Control-Allow-Origin' => $origin,
            'Access-Control-Allow-Credentials' => $this->config['allow-credentials'],
            'Access-Control-Allow-Headers' => $this->config['allow-headers'],
            'Access-Control-Allow-Methods' => $this->config['allow-methods'],
        ];

        if ($request->getMethod() == 'OPTIONS') {
            return new Response(HttpStatusCode::OK, $headers);
        }

        $response = MiddlewareRunner::next($request);
  
        /**
         * @var $response ResponseInterface;
         */
        return $response->withHeader('Access-Control-Allow-Origin', $origin)
            ->withHeader('Access-Control-Allow-Credentials', $this->config['allow-credentials'])
            ->withHeader('Access-Control-Allow-Methods', $this->config['allow-methods']);
    }
}
